import { httpError, Inject, Provide } from '@midwayjs/core'
import { Context } from '@midwayjs/koa'
import { InjectEntityModel } from '@midwayjs/typeorm'
import { Repository } from 'typeorm'

import { DeleteDTO } from '@/dto'
import { SysMenuEntity } from '@/entity'
import { StateService } from '@/service'
import { TransformUtil } from '@/util'

import { CreateMenuDTO, FindMenuListDTO, UpdateMenuDTO } from './menu.dto'

@Provide()
export class MenuService {
  @Inject()
  ctx: Context

  @InjectEntityModel(SysMenuEntity)
  menuModel: Repository<SysMenuEntity>

  async handleFindList(dto: FindMenuListDTO) {
    return await this.menuModel.find({
      where: {
        ...dto
      }
    })
  }

  async handleFindTree() {
    const data = await this.menuModel.find({
      where: { status: '0', visible: '0' }
    })

    return TransformUtil.listToTree(data, {
      title: 'menuName',
      key: 'menuId',
      parentKey: 'parentId'
    })
  }

  async handleCreate(dto: CreateMenuDTO) {
    const stateService = await this.ctx.requestContext.getAsync(StateService)

    const jwtPayload = stateService.getJwtPayload()

    const menu = new SysMenuEntity()

    Object.assign<any, any, Partial<SysMenuEntity>>(menu, dto, {
      createBy: jwtPayload.userName
    })

    await this.menuModel.save(menu)
  }

  async handleUpdate(id: string, dto: UpdateMenuDTO) {
    const stateService = await this.ctx.requestContext.getAsync(StateService)

    const jwtPayload = stateService.getJwtPayload()

    const menu = await this.menuModel.findOne({ where: { menuId: id } })

    if (!menu) {
      this.ctx.throw(new httpError.BadRequestError('菜单不存在'))
    }

    Object.assign<any, any, Partial<SysMenuEntity>>(menu, dto, {
      updateBy: jwtPayload.userName
    })

    await this.menuModel.save(menu)
  }

  async handleDelete(dto: DeleteDTO) {
    const { ids } = dto

    await this.menuModel.delete(ids)
  }
}
